home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1993…stman Always Clicks Twice / ADC Developer CD (1993-01) (''The Postman Always Clicks Twice'')_iso / Dev.CD 199301.iso / Technical Documentation / Sample Code / DTS.Lib & Samples / DTS.Lib / AERequired.c < prev    next >
Encoding:
C/C++ Source or Header  |  1992-10-22  |  9.2 KB  |  324 lines  |  [TEXT/MPS ]

  1. /*
  2. ** Apple Macintosh Developer Technical Support
  3. **
  4. ** Program:        DTS.Lib
  5. ** File:        AERequired.c
  6. ** Written by:  Eric Soldan
  7. **
  8. ** Copyright © 1990-1991 Apple Computer, Inc.
  9. ** All rights reserved.
  10. **
  11. ** This code implements the required AppleEvents, specific to DTS.Lib.
  12. */
  13.  
  14.  
  15.  
  16. /*****************************************************************************/
  17.  
  18.  
  19.  
  20. #include "DTS.Lib2.h"
  21. #include "DTS.Lib.Common.h"
  22. #include "DTS.Lib.protos.h"
  23.  
  24. #ifndef __GESTALTEQU__
  25. #include <GestaltEqu.h>
  26. #endif
  27.  
  28. #include "Utilities.h"
  29.  
  30.  
  31.  
  32. /*****************************************************************************/
  33.  
  34.  
  35.  
  36. #define kTimeOutInTicks (60 * 30)    /* 30 second timeout. */
  37.  
  38. static pascal OSErr    DoAEOpenApplication(AppleEvent *message, AppleEvent *reply, long refcon);
  39. static pascal OSErr    DoAEOpenDocuments(AppleEvent *message, AppleEvent *reply, long refcon);
  40. static pascal OSErr    DoAEPrintDocuments(AppleEvent *message, AppleEvent *reply, long refcon);
  41. static pascal OSErr    DoAEQuitApplication(AppleEvent *message, AppleEvent *reply, long refcon);
  42. static OSErr        OpenDocEventHandler(AppleEvent *message, AppleEvent *reply, short mode);
  43.  
  44.  
  45.  
  46. /*****************************************************************************/
  47.  
  48.  
  49.  
  50. static AEHandler keywordsToInstall[] = {
  51.     { kCoreEventClass,        kAEOpenApplication,        (ProcPtr)DoAEOpenApplication },
  52.     { kCoreEventClass,        kAEOpenDocuments,        (ProcPtr)DoAEOpenDocuments },
  53.     { kCoreEventClass,        kAEPrintDocuments,        (ProcPtr)DoAEPrintDocuments },
  54.     { kCoreEventClass,        kAEQuitApplication,        (ProcPtr)DoAEQuitApplication }
  55.         /* The above are the four required AppleEvents. */
  56. };
  57.  
  58. Boolean        gHasAppleEvents = false;
  59. Boolean        gHasPPCToolbox  = false;
  60.  
  61.  
  62.  
  63. /*****************************************************************************/
  64.  
  65.  
  66.  
  67. extern Boolean        gQuitApplication, gNoDefaultDocument, gInBackground;
  68. extern Cursor        *gCursorPtr;
  69. extern short        gPrintPage;
  70. extern SFTypeList    gTypeList;
  71.  
  72.  
  73.  
  74. /*****************************************************************************/
  75. /*****************************************************************************/
  76.  
  77.  
  78.  
  79. /* Intializes AppleEvent dispatcher table for the required events.  It also
  80. ** determines if the machine is PPCBrowser and AppleEvent capable.  If so,
  81. ** the booleans gHasAppleEvents and gHasPPCToolbox are set true.  This function
  82. ** must be the first AppleEvents initialization DTS.framework function called, as the
  83. ** other functions depend on the booleans being set correctly. */
  84.  
  85. #pragma segment AppleEvents
  86. OSErr    InitRequiredAppleEvents(void)
  87. {
  88.     OSErr    err;
  89.     long    result;
  90.     short    i;
  91.  
  92.     gHasPPCToolbox  = (Gestalt(gestaltPPCToolboxAttr, &result) ? false : result != 0);
  93.     gHasAppleEvents = (Gestalt(gestaltAppleEventsAttr, &result) ? false : result != 0);
  94.  
  95.     if (gHasAppleEvents) {
  96.         for (i = 0; i < (sizeof(keywordsToInstall) / sizeof(AEHandler)); ++i) {
  97.             err = AEInstallEventHandler(
  98.                 keywordsToInstall[i].theEventClass,    /* What class to install.  */
  99.                 keywordsToInstall[i].theEventID,    /* Keywords to install.    */
  100.                 keywordsToInstall[i].theHandler,    /* The AppleEvent handler. */
  101.                 0L,                                    /* Unused refcon.           */
  102.                 false                                /* Only for our app.       */
  103.             );
  104.             if (err) {
  105.                 Alert(rErrorAlert, (ModalFilterProcPtr)AlertFilter);
  106.                 return(err);
  107.             }
  108.         }
  109.     }
  110.  
  111.     return(noErr);
  112. }
  113.  
  114.  
  115.  
  116. /*****************************************************************************/
  117.  
  118.  
  119.  
  120. /* This function opens a new DTS.framework document due to an AppleEvents request. */
  121.  
  122. #pragma segment AppleEvents
  123. static pascal OSErr    DoAEOpenApplication(AppleEvent *message, AppleEvent *reply, long refcon)
  124. {
  125. #pragma unused (message, reply, refcon)
  126.  
  127.     FileRecHndl    frHndl;
  128.     OSErr        err;
  129.  
  130.     gCursorPtr = nil;
  131.         /* Force re-calc of cursor region and cursor to use. */
  132.  
  133.     err = noErr;
  134.     if (!gNoDefaultDocument) {
  135.         err = NewDocument(&frHndl, gTypeList[0], true);
  136.         if (!err)
  137.             if (err = DoNewWindow(frHndl, nil, FrontWindow(), (WindowPtr)-1))
  138.                 DisposeDocument(frHndl);
  139.     }
  140.  
  141.     return(err);
  142. }
  143.  
  144.  
  145.  
  146. /*****************************************************************************/
  147.  
  148.  
  149.  
  150. /* This function opens existing DTS.framework documents due to an AppleEvents request. */
  151.  
  152. #pragma segment AppleEvents
  153. static pascal OSErr    DoAEOpenDocuments(AppleEvent *message, AppleEvent *reply, long refcon)
  154. {
  155. #pragma unused (refcon)
  156.  
  157.     gCursorPtr = nil;        /* Force re-calc of cursor region and cursor to use. */
  158.     return(OpenDocEventHandler(message, reply, 0));
  159.         /* The 0 means regular open document. */
  160. }
  161.  
  162.  
  163.  
  164. /*****************************************************************************/
  165.  
  166.  
  167.  
  168. /* This function prints DTS.framework documents due to an AppleEvents request. */
  169.  
  170. #pragma segment AppleEvents
  171. static pascal OSErr    DoAEPrintDocuments(AppleEvent *message, AppleEvent *reply, long refcon)
  172. {
  173. #pragma unused (refcon)
  174.  
  175.     short                openMode;
  176.     ProcessSerialNumber    cpsn, fpsn;
  177.     Boolean                procsSame;
  178.  
  179.     gCursorPtr = nil;        /* Force re-calc of cursor region and cursor to use. */
  180.  
  181.     openMode = 1;
  182.     if (!AEInteractWithUser(kTimeOutInTicks, nil, nil))
  183.         ++openMode;
  184.  
  185.     GetCurrentProcess(&cpsn);        /* We may have been moved to the front. */
  186.     GetFrontProcess(&fpsn);
  187.     SameProcess(&cpsn, &fpsn, &procsSame);
  188.     gInBackground = !procsSame;
  189.  
  190.     return(OpenDocEventHandler(message, reply, openMode));
  191.         /* openMode is either 1 or 2, depending if user interaction is okay. */
  192. }
  193.  
  194.  
  195.  
  196. /*****************************************************************************/
  197.  
  198.  
  199.  
  200. /* This function sets a quit flag so that DTS.framework will quit due to an
  201. ** AppleEvents request. */
  202.  
  203. #pragma segment AppleEvents
  204. static pascal OSErr    DoAEQuitApplication(AppleEvent *message, AppleEvent *reply, long refcon)
  205. {
  206. #pragma unused (message, reply, refcon)
  207.  
  208.     OSErr    err;
  209.  
  210.     gCursorPtr = nil;
  211.         /* Force re-calc of cursor region and cursor to use. */
  212.  
  213.     if (DisposeAllWindows()) {
  214.         gQuitApplication = true;
  215.         err = noErr;
  216.     }
  217.     else err = errAEEventNotHandled;
  218.         /* All windows didn't close because user cancelled the quit. */
  219.  
  220.     return(err);
  221. }
  222.  
  223.  
  224.  
  225. /*****************************************************************************/
  226.  
  227.  
  228.  
  229. /* Called when we recieve an AppleEvent with an ID of "kAEOpenDocuments".
  230. ** This routine gets the direct parameter, parses it up into little FSSpecs,
  231. ** and opens each indicated file.  It also shows the technique to be used in
  232. ** determining if you are doing everything the AppleEvent record is telling
  233. ** you.  Parameters can be divided up into two groups: required and optional.
  234. ** Before executing an event, you must make sure that you've read all the
  235. ** required events.  This is done by making an "any more?" call to the
  236. ** AppleEvent manager. */
  237.  
  238. #pragma segment AppleEvents
  239. static OSErr    OpenDocEventHandler(AppleEvent *message, AppleEvent *reply, short mode)
  240. {
  241. #pragma unused (reply)
  242.  
  243.     OSErr        err;
  244.     OSErr        err2;
  245.     AEDesc        theDesc;
  246.     FSSpec        theFSS;
  247.     short        loop;
  248.     long        numFilesToOpen;
  249.     AEKeyword    ignoredKeyWord;
  250.     DescType    ignoredType;
  251.     Size        ignoredSize;
  252.     FileRecHndl    frHndl;
  253.     WindowPtr    docWindow;
  254.  
  255.     theDesc.dataHandle = nil;
  256.         /* Make sure disposing of the descriptors is okay in all cases.
  257.         ** This will not be necessary after 7.0b3, since the calls that
  258.         ** attempt to create the descriptors will nil automatically
  259.         ** upon failure. */
  260.  
  261.     if (err = AEGetParamDesc(message, keyDirectObject, typeAEList, &theDesc))
  262.         return(err);
  263.  
  264.     if (!MissedAnyParameters(message)) {
  265.  
  266. /* Got all the parameters we need.  Now, go through the direct object,
  267. ** see what type it is, and parse it up. */
  268.  
  269.         err = AECountItems(&theDesc, &numFilesToOpen);
  270.         if (!err) {
  271.             /* We have numFilesToOpen that need opening, as either a window
  272.             ** or to be printed.  Go to it... */
  273.  
  274.             for (loop = 1; ((loop <= numFilesToOpen) && (!err)); ++loop) {
  275.                 err = AEGetNthPtr(        /* GET NEXT IN THE LIST...         */
  276.                     &theDesc,            /* List of file names.             */
  277.                     loop,                /* Item # in the list.             */
  278.                     typeFSS,            /* Item is of type FSSpec.         */
  279.                     &ignoredKeyWord,    /* Returned keyword -- we know.  */
  280.                     &ignoredType,        /* Returned type -- we know.     */
  281.                     (Ptr)&theFSS,        /* Where to put the FSSpec info. */
  282.                     sizeof(theFSS),        /* Size of the FSSpec info.         */
  283.                     &ignoredSize        /* Actual size -- we know.         */
  284.                 );
  285.                 if (err) break;
  286.  
  287.                 err = OpenDocument(&frHndl, &theFSS, fsRdWrPerm);
  288.                 if (err) break;
  289.  
  290.                 gPrintPage = mode;
  291.                     /* Open the window off-screen if we are printing.
  292.                     ** We use the gPrintPage global to flag this.  Normally, the
  293.                     ** gPrintPage global is to tell ImageDocument if we are imaging
  294.                     ** to the window or to paper.  We don't need it for this yet,
  295.                     ** as we can't image the document until it is opened.  DoNewWindow()
  296.                     ** uses gPrintPage as a flag to open the window off-screen, but
  297.                     ** visible, so that PrintMonitor can use the title of the window
  298.                     ** as the document name that is being printed. */
  299.  
  300.                 if (err = DoNewWindow(frHndl, &docWindow, FrontWindow(), (WindowPtr)-1))
  301.                     DisposeDocument(frHndl);
  302.                 else {
  303.                     if (gPrintPage) {
  304.                         err  = PrintDocument(frHndl, (mode == 2), (loop == 1));
  305.                         mode = 1;    /* No interaction mode (mode == 2) only valid
  306.                                     ** for the first printed document. */
  307.                         DisposeDocument(frHndl);
  308.                         DisposeAnyWindow(docWindow);
  309.                     }
  310.                 }
  311.                 gPrintPage = 0;
  312.                     /* Put the ImageDocument controlling global back to normal. */
  313.             }
  314.         }
  315.     }
  316.     DonePrinting();        /* Clean up after printing, if we did any. */
  317.  
  318.     err2 = AEDisposeDesc(&theDesc);
  319.     return(err ? err : err2);
  320. }
  321.  
  322.  
  323.  
  324.